﻿using System;
using System.Collections.Generic;
using System.Data;
using System.Data.OleDb;
using System.Data.SqlClient;
using System.Linq;
using System.Text;

namespace MaxZhang.EasyEntities.EasyDesigner.Core
{
    public class SqlServerDbSchema : IDbSchema
    {
        public SqlServerDbSchema(string connString)
        {
            
            Conn = new SqlConnection(connString);
        }

        private SqlConnection Conn;

        public List<DbEntity> GetTables()
        {
            List<DbEntity> tables = new List<DbEntity>(15);
            Conn.Open();
            var shemaTable1 = Conn.GetSchema("Tables");

            foreach (DataRow tableRow in shemaTable1.Rows)
            {
                if (tableRow["TABLE_TYPE"].ToString() != "BASE TABLE")
                    continue;
                
                var tableName = tableRow["TABLE_NAME"].ToString();
                DbEntity table = new DbEntity();
                table.Name = tableName;
                table.Memo = string.Format("({0})",tableName);


                var command = Conn.CreateCommand();
                command.CommandText = string.Format(@"Select top 1 * From {0} Where 1=0", tableName);
                SqlDataAdapter sda = new SqlDataAdapter(command);
                DataTable shemaTable2 = new DataTable(tableName);
                sda.FillSchema(shemaTable2,SchemaType.Mapped);
                var columns = shemaTable2.Columns.Cast<DataColumn>();

                DataTable columnTable = Conn.GetSchema("Columns", new string[] { null, null, tableName, null });

                table.Keys = string.Join(",",shemaTable2.PrimaryKey.Select(dc => dc.ColumnName));

                foreach (DataRow columnRow in columnTable.Rows)
                {
                   var dataType = columnRow["DATA_TYPE"].ToString();
                   var charLength = columnRow["CHARACTER_MAXIMUM_LENGTH"].ToString();
                   var numberLength = columnRow["NUMERIC_PRECISION"].ToString();
                   var numberDot = columnRow["NUMERIC_SCALE"].ToString();
                   
                   var thatColumn = columns.First(c => c.ColumnName == columnRow["COLUMN_NAME"].ToString());

                   DbProperty property = new DbProperty();
                   property.IsPrimaryKey = shemaTable2.PrimaryKey.Any(k => k.ColumnName == thatColumn.ColumnName);
                   property.DefaultValue = thatColumn.DefaultValue.ToString();
                   property.Name = thatColumn.ColumnName;
                   property.IsIdentity = thatColumn.AutoIncrement;
                   property.IdentitySpeed = Convert.ToInt32(thatColumn.AutoIncrementSeed);
                   property.IdentitySetp = Convert.ToInt32(thatColumn.AutoIncrementStep);
                   property.IsNull = thatColumn.AllowDBNull;
                   property.DataType = dataType;
                   property.PropertyType = thatColumn.DataType;
                   property.PropertyTypeName = thatColumn.DataType.AssemblyQualifiedName;
                   this.GetDataType(ref property , charLength,numberLength,numberDot);
                   
                   table.Propertys.Add(property);

                }

                tables.Add(table);
            }



            Conn.Close();

            return tables;
        }


       private void GetDataType(ref DbProperty property, string charLength,string numberLength ,string numberDot)
       {
           Type type = property.PropertyType;
           if (type == typeof(int) || type == typeof(decimal) || type == typeof(double) || type == typeof(float))
           {
               if (!string.IsNullOrEmpty(numberLength))
               {
                   property.DataLength = Convert.ToInt32(numberLength);
                   if(!string.IsNullOrEmpty(numberDot))
                       property.DataDotLength = Convert.ToInt32(numberDot);
               }
           }
           else if(type==typeof(DateTime) || type==typeof(TimeSpan))
           {
               
           }
           else if (type == typeof(string) || type == typeof(StringBuilder))
           {
               if (!string.IsNullOrEmpty(charLength))
               {
                   property.DataLength = Convert.ToInt32(charLength);
                   property.DataDotLength = 0;
               }
           }

       }



    }
}
